home *** CD-ROM | disk | FTP | other *** search
Text File | 1994-10-04 | 10.8 KB | 343 lines | [TEXT/MMCC] |
- //========================================================================================
- // Program Listings from "Scripting the Finder from your own Application"
- // develop Issue 20
- // Greg Anderson
- //========================================================================================
- #include "AppleEventUtilities.h"
- #include "AERegistry.h"
- #include "AEObjects.h"
- #include "FinderRegistry.h"
- #include "Exceptions.h"
-
-
-
- //----------------------------------------------------------------------------------------
- // Listing 1
- //
- // This function gets the address of the Finder running on this machine. It walks the
- // process list rather than just building an address for the Finder's creator type,
- // 'MACS', because there are other applications whose creator type is 'MACS'.
- //----------------------------------------------------------------------------------------
- TDescriptor GetAddressOfFinder()
- {
- ProcessSerialNumber psn;
- ProcessInfoRec theProc;
- TDescriptor finderAddressDescriptor;
-
- psn.highLongOfPSN = 0;
- psn.lowLongOfPSN = kNoProcess;
-
- //
- // Initialize fields in the ProcessInfoRec,
- // or we'll have memory hits in random locations
- //
- theProc.processInfoLength = sizeof( ProcessInfoRec );
- theProc.processName = nil;
- theProc.processAppSpec = nil;
- theProc.processLocation = nil;
-
- while(true)
- {
- FailErr(GetNextProcess(&psn));
- if( (psn.highLongOfPSN == 0) && (psn.lowLongOfPSN == kNoProcess) )
- Throw(procNotFound);
-
- FailErr(GetProcessInformation(&psn, &theProc));
- if( (theProc.processType == 'FNDR' ) && (theProc.processSignature == 'MACS') )
- break;
- }
- finderAddressDescriptor.MakeProcessSerialNumber(psn);
-
- return finderAddressDescriptor;
- } // GetAddressOfFinder
-
- //----------------------------------------------------------------------------------------
- // Listing 2
- //
- // This function returns the items that are currently selected in the Finder.
- //----------------------------------------------------------------------------------------
- TDescriptor GetFinderSelection(DescType desiredType)
- {
- TAEvent ae;
- OSErr err = noErr;
-
- //
- // Get the address of the Finder and make a "Set Data" event
- //
- TDescriptor target = GetAddressOfFinder();
- ae.MakeAppleEvent(kAECoreSuite, kAEGetData, target);
- target.Dispose();
-
- //
- // Make an object specifier for the property we want to set,
- // and put it into the direct object of our event
- //
- TDescriptor directObjectSpecifier;
- TDescriptor keyData;
- TDescriptor nullDescriptor;
-
- keyData.MakeDescType(pSelection);
- directObjectSpecifier.MakeObjectSpecifier( cProperty,
- nullDescriptor,
- formPropertyID,
- keyData,
- true);
- ae.PutDescriptor(keyDirectObject, directObjectSpecifier);
- directObjectSpecifier.Dispose();
-
- //
- // Request FSSpecs back from the Get Data event.
- //
- // The Object Support Library requires that the
- // requested data type be stored in a list of types,
- // so we coerce the 'typeType' descriptor into a list
- // of one descriptor. The Finder does not require
- // this, but some other applications might, since it
- // is part of the OSL spec.
- //
- TDescriptor dataDescriptor;
-
- dataDescriptor.MakeDescType(typeAlias);
- dataDescriptor.CoerceInPlace(typeAEList);
- ae.PutDescriptor(keyAERequestedType, dataDescriptor);
- dataDescriptor.Dispose();
-
- //
- // It is generally a bad idea to use kAEWaitReply,
- // because it prevents your application from processing
- // other events. There are a number of potential solutions:
- //
- // Use kAEQueueReply, and process the reply when it is
- // returned from WaitNextEvent. The disadvantage is that
- // the processing of the reply must be done separately
- // from the code that sets up to do the send
- //
- // Provide a filter proc to AESend that processes
- // events while your application is waiting for the reply.
- // The disadvantage of doing this is that the event
- // handling of your application is complicated, and
- // may become nested if events need to be sent to
- // process an incoming message
- //
- // Pass kImmediateTimeout as the timeout value for
- // AESend. When the reply event is accessed, an
- // error is returned if the reply has not yet arrived.
- // This method is best employeed in conjunction with
- // a threads package, so that the thread that sends
- // the message can block until the reply arrives.
- // See the article on Futures by Michael Gough in
- // d e v e l o p issue #7.
- //
- TAEvent reply;
- ae.Send(&reply, kAEWaitReply);
-
- //
- // Extract the result from the reply
- //
- TDescriptor selectedItems = reply.GetDescriptor(keyAEResult);
- reply.Dispose();
- ae.Dispose();
-
- return selectedItems;
- } // GetFinderSelection
-
- //----------------------------------------------------------------------------------------
- // Listing 3
- //
- // This function returns the owner (folder, file, disk or trash) of the frontmost window.
- //----------------------------------------------------------------------------------------
- TDescriptor Listing3()
- {
- TAEvent ae;
-
- TDescriptor target = GetAddressOfFinder();
- ae.MakeAppleEvent(kAECoreSuite, kAEGetData, target);
- target.Dispose();
-
- TDescriptor directObjectSpecifier;
- TDescriptor frontWindowSpecifier;
- TDescriptor keyData;
- TDescriptor nullDescriptor;
-
- keyData.MakeLong(1);
- frontWindowSpecifier.MakeObjectSpecifier(cWindow, nullDescriptor, formAbsolutePosition, keyData, true);
- keyData.MakeDescType(cObject);
- directObjectSpecifier.MakeObjectSpecifier(cProperty, frontWindowSpecifier, formPropertyID, keyData, true);
- ae.PutDescriptor(keyDirectObject, directObjectSpecifier);
- directObjectSpecifier.Dispose();
-
- TDescriptor dataDescriptor;
-
- dataDescriptor.MakeDescType(typeAlias);
- dataDescriptor.CoerceInPlace(typeAEList);
- ae.PutDescriptor(keyAERequestedType, dataDescriptor);
- dataDescriptor.Dispose();
-
- TAEvent reply;
- ae.Send(&reply, kAEWaitReply);
-
- //
- // Extract the result from the reply
- //
- TDescriptor frontWindowOwner = reply.GetDescriptor(keyAEResult);
- reply.Dispose();
- ae.Dispose();
-
- return frontWindowOwner;
- }
-
-
- //----------------------------------------------------------------------------------------
- // Listing 4
- //
- // This function deletes the custom icon from every item (file or folder) currently
- // selected in the Finder.
- //----------------------------------------------------------------------------------------
- void Listing4()
- {
- TAEvent ae;
-
- TDescriptor target = GetAddressOfFinder();
- ae.MakeAppleEvent(kAECoreSuite, kAESetData, target);
- target.Dispose();
-
- TDescriptor directObjectSpecifier;
- TDescriptor selectionSpecifier;
- TDescriptor keyData;
- TDescriptor nullDescriptor;
-
- keyData.MakeDescType(pSelection);
- selectionSpecifier.MakeObjectSpecifier(cProperty, nullDescriptor, formPropertyID, keyData, true);
- keyData.MakeDescType(pIconBitmap);
- directObjectSpecifier.MakeObjectSpecifier(cProperty, selectionSpecifier, formPropertyID, keyData, true);
- ae.PutDescriptor(keyDirectObject, directObjectSpecifier);
- directObjectSpecifier.Dispose();
-
- TDescriptor emptyList;
-
- emptyList.MakeEmptyList();
- ae.PutDescriptor(keyAEData, emptyList);
- emptyList.Dispose();
-
- TAEvent reply;
- ae.Send(&reply, kAENoReply);
- ae.Dispose();
- }
-
- //----------------------------------------------------------------------------------------
- // Listing 5
- //
- // This function makes sure that the Finder's representation for the specified
- // container is up-to-date with what is on disk. It is useful to tell the Finder
- // to do this whenever your application writes into a given folder; this will make
- // sure that the Finder always re-sorts the window so that the modification date
- // of the item is correct (to name one example).
- //----------------------------------------------------------------------------------------
- void UpdateFinderContainer(FSSpec& changedContainer)
- {
- TAEvent ae;
-
- TDescriptor target = GetAddressOfFinder();
- ae.MakeAppleEvent(kAEFinderSuite, kAEUpdate, target);
- target.Dispose();
-
- TDescriptor directObjectSpecifier;
-
- directObjectSpecifier.MakeFSS(changedContainer);
- ae.PutDescriptor(keyDirectObject, directObjectSpecifier);
- directObjectSpecifier.Dispose();
-
- TAEvent reply;
- ae.Send(&reply, kAENoReply);
- ae.Dispose();
- }
-
-
- //----------------------------------------------------------------------------------------
- // Listing 6
- //
- // This listing shares every folder currently selected in the Finder.
- //----------------------------------------------------------------------------------------
- void Listing6()
- {
- TAEvent ae;
-
- TDescriptor target = GetAddressOfFinder();
- ae.MakeAppleEvent(kAECoreSuite, kAESetData, target);
- target.Dispose();
-
- TDescriptor selectionSpecifier;
- TDescriptor keyData;
- TDescriptor nullDescriptor;
-
- keyData.MakeDescType(pSelection);
- selectionSpecifier.MakeObjectSpecifier(cProperty, nullDescriptor, formPropertyID, keyData, true);
-
- TDescriptor everySpecifier;
- keyData.MakeOrdinal(kAEAll);
- everySpecifier.MakeObjectSpecifier(cFolder, selectionSpecifier, formAbsolutePosition, keyData, true);
-
- TDescriptor directObjectSpecifier;
- keyData.MakeDescType(pSharing);
- directObjectSpecifier.MakeObjectSpecifier(cProperty, everySpecifier, formPropertyID, keyData, true);
- ae.PutDescriptor(keyDirectObject, directObjectSpecifier);
- directObjectSpecifier.Dispose();
-
- TDescriptor sharedSetting;
-
- sharedSetting.MakeBoolean(true);
- ae.PutDescriptor(keyAEData, sharedSetting);
- sharedSetting.Dispose();
-
- TAEvent reply;
- ae.Send(&reply, kAENoReply);
- ae.Dispose();
- }
-
- //----------------------------------------------------------------------------------------
- // Listing 7
- //
- // This listing moves the item named "x" on the desktop into the preferences folder
- // and sets its location to (10, 10). If the preferences folder is open, this location
- // will be in local coordinates. If the window is not open, then the coordinates
- // will be in the same coordinate space written to disk in the Finder Info field.
- //----------------------------------------------------------------------------------------
- void Listing7()
- {
- TAEvent ae;
-
- TDescriptor target = GetAddressOfFinder();
- ae.MakeAppleEvent(kAECoreSuite, kAEMove, target);
- target.Dispose();
-
- TDescriptor directObjectSpecifier;
- TDescriptor keyData;
- TDescriptor nullDescriptor;
-
- keyData.MakeString("\px");
- directObjectSpecifier.MakeObjectSpecifier(cObject, nullDescriptor, formName, keyData, true);
- ae.PutDescriptor(keyDirectObject, directObjectSpecifier);
- directObjectSpecifier.Dispose();
-
- TDescriptor preferencesSpecifier;
-
- keyData.MakeDescType(pPreferencesFolder);
- preferencesSpecifier.MakeObjectSpecifier(cProperty, nullDescriptor, formPropertyID, keyData, true);
- ae.PutDescriptor(keyAEInsertHere, preferencesSpecifier);
-
- Point destinationPosition;
- destinationPosition.h = 10;
- destinationPosition.v = 10;
-
- keyData.MakePoint(destinationPosition);
- keyData.CoerceInPlace(typeAEList);
- ae.PutDescriptor(keyLocalPositionList, keyData);
- keyData.Dispose();
-
- TAEvent reply;
- ae.Send(&reply, kAENoReply);
-
- ae.Dispose();
- }
-
-